package ve.com.wayoyo.wuml_case.DibujoDiagramas;

import java.util.ArrayList;

import ve.com.wayoyo.wuml_case.Painter;
import android.graphics.Canvas;
import android.graphics.Point;
import android.graphics.Rect;
import android.graphics.RectF;

public class CompObjeto extends Componente {
	final static int MaxCharacterPerLine = 10;
	final static int VerticalMargin = 25;
	final static int HorizontalMargin = 30;
	final static int MinBaseLineHeight = 140;
	final static int SizeSteeps = 20;
	final static int MinLifeBarSize = 100;
	final static int LifeBarWidht = 30;
	final static int InitialBarDistance = 50;
	
	private ArrayList<String> TextLine = new ArrayList<String>();
	private String longestString = "Caso";
	private Point textPoint;
	private int textLineSpan;
	private int baseLineHeight = 500;
	private ArrayList<Componente> _subComponentes = new ArrayList<Componente>();


	public CompObjeto() {
		_centerPoint = new Point(0, 0);
		textPoint = new Point();
		textLineSpan = 0;

		_connectionPoints = new Point[16];
		for (int i = 0; i < _connectionPoints.length; i++) {
			_connectionPoints[i] = new Point();
		}
		isConnectable = false;
	}

	@Override
	public void setTitulo(String titulo) {
		Titulo = titulo;
		TextLine = DividirTitulo(titulo);
		int aux;
		for (String value : TextLine) {
			aux = value.length();
			if (aux > longestString.length()) {
				longestString = value;
			}
		}
		actualizarPuntoCentral();
		actualizarAchorsPoints();
	}

	@Override
	public void Dibujar(Canvas c, boolean isFcoused, float globalScale,
			int offSetX, int offSetY) {

		int posX = _centerPoint.x + offSetX;
		int posY = _centerPoint.y + offSetY;
		int textWidht;
		RectF borde = new RectF();
		// Dibujamos el texto
		for (int i = 0; i < TextLine.size(); i++) {
			textWidht = (int) Painter.getInstancia()
					.getTextPaint(false, globalScale)
					.measureText(TextLine.get(i));
			c.drawText(TextLine.get(i), ((posX * globalScale) - textWidht / 2),
					((textPoint.y + offSetY)
							- (textLineSpan * (TextLine.size() - i - 1)) - 2)
							* globalScale,
					Painter.getInstancia().getUnderLineTextPaint(false, globalScale));
		}

		// Dibujamos el contorno
		borde.set((posX - (_width / 2)) * globalScale, (posY - (_height / 2))
				* globalScale, (posX + (_width / 2)) * globalScale,
				(posY + (_height / 2)) * globalScale);
		c.drawRect(borde,Painter.getInstancia().getBorderPaint(_currentState));

		c.drawLine((posX)*globalScale, (posY+(_height/2))*globalScale, (posX)*globalScale, (posY+(_height/2)+baseLineHeight)*globalScale, Painter.getInstancia().getBorderPaint(_currentState));
		
		// Dibujamos la barra de vida del objeto
		
	/*	RectF LifeBar = new RectF();
		LifeBar.set(((LifeBarCenterPoint.x + offSetX) - (LifeBarWidht/ 2)) * globalScale, ((LifeBarCenterPoint.y + offSetY) - (LifeBarHeight / 2))
				* globalScale, ((LifeBarCenterPoint.x + offSetX) + (LifeBarWidht / 2)) * globalScale,
				((LifeBarCenterPoint.y + offSetY) + (LifeBarHeight / 2)) * globalScale);
		c.drawRect(LifeBar, Painter.getInstancia().getBlockPaint(_currentState, true));
	*/	
		// Dibujamos los conectores
		for(Componente value : _subComponentes){
			value.Dibujar(c, isFcoused, globalScale, offSetX, offSetY);
			
		}
		for (CompConector value : _conectorsBegining) {
			value.Dibujar(c, isFcoused, globalScale, offSetX, offSetY);
		}

		
	}

	@Override
	public boolean CalcularVisibilidad(int offSetX, int offSetY,
			float GlobalScale) {
		// TODO Auto-generated method stub
		return false;
	}

	@Override
	public boolean calcularTouch(Point touch) {
		boolean respuesta = false;
		if ((touch.x <= Anchor.x + _width) && (touch.x >= Anchor.x)) {
			if ((touch.y <= Anchor.y + _height) && (touch.y >= Anchor.y)) {
				respuesta = true;
			}
		}
		return respuesta;
	}
	
	public Componente calcularTouchBarra(Point touch){
		Componente respuesta = null;
		for (Componente value : _subComponentes) {
			if(value.calcularTouch(touch)){
				respuesta = value;
				break;
			}
		}
		return respuesta;
	}

	@Override
	public CompConector calcularTouchConectores(Point touch) {
		CompConector respuesta = null;
		for (Componente value : _subComponentes) {
			respuesta = value.calcularTouchConectores(touch);
			if(respuesta != null){
				break;
			}
		}
		return respuesta;
	}

	@Override
	public void actualizarAchorsPoints() {

	}

	@Override
	public void actualizarPuntoCentral() {
		Rect mBounds = new Rect();
		int TotalTextHeight = 0;
		for (int i = 0; i < TextLine.size(); i++) {
			Painter.getInstancia().getTextPaint(false, 1)
					.getTextBounds(TextLine.get(i), 0, 2, mBounds);
			TotalTextHeight += (int) ((float) mBounds.height() * 1.2);
		}
		_width = Painter.getInstancia().getTextPaint(false, 1)
				.measureText(longestString)
				+ HorizontalMargin * 2;
		_height = TotalTextHeight + VerticalMargin * 2;
		_centerPoint.x = (int) (Anchor.x + (_width / 2));
		_centerPoint.y = (int) (Anchor.y + (_height / 2));
		textPoint.x = (int) (_centerPoint.x - (Painter.getInstancia()
				.getTextPaint(false, 1).measureText(longestString) / 2));
		textPoint.y = _centerPoint.y + (TotalTextHeight / 2);
		if (TextLine.size() > 0) {
			textLineSpan = TotalTextHeight / TextLine.size();
		}
		
		for (Componente value : _subComponentes) {
			if(value instanceof CompLifeBar){
				((CompLifeBar)value).align(_centerPoint.x);
				((CompLifeBar)value).setBounds((int)(Anchor.y + (_height)), (int)(Anchor.y + (_height)+baseLineHeight));
			}
		}
		
	}

	@Override
	public String generarDOM() {
		String DOM = "\t<Componente Tipo=\"Objeto\" Titulo=\"" + Titulo
				+ "\" ID=\"" + ID + "\" AnchorX=\"" + Anchor.x
				+ "\" AnchorY=\"" + Anchor.y +"\" BaseLineHeight=\"" + baseLineHeight +"\">\n";
		for (Componente value : _subComponentes) {
			DOM = DOM + value.generarDOM();
		}
		DOM = DOM + "\t</Componente>\n";
		return DOM;
	}

	@Override
	public String getConectorsDOM() {
		String DOM = "";
		for (Componente value : _subComponentes) {
			DOM = DOM + value.getConectorsDOM();
		}
		return DOM;
	}

	@Override
	public void calculoLongitud() {
		// TODO Auto-generated method stub

	}

	@Override
	public Point requestConnectionPoint(CompConector connector, int mode,
			Point otherCompCenter) {
		float distMin = Float.MAX_VALUE;
		float dX = 0;
		float dY = 0;
		float disActual;
		int CP_MasCercano = 0; // Punto de conexion con menor distancia
		for (int i = 0; i < _connectionPoints.length; i++) {
			dX = _connectionPoints[i].x - otherCompCenter.x;
			dY = _connectionPoints[i].y - otherCompCenter.y;
			disActual = (float) Math.sqrt(dX * dX + dY * dY);
			if (disActual < distMin) {
				distMin = disActual;
				CP_MasCercano = i;
			}
		}
		return _connectionPoints[CP_MasCercano];

	}

	public ArrayList<String> DividirTitulo(String titulo) {
		ArrayList<String> respuesta = new ArrayList<String>();
		String[] arreglo = titulo.split(" ");
		String linea = "";
		int acumulatedChar = 0;
		for (int i = 0; i < arreglo.length; i++) {
			acumulatedChar += arreglo[i].length();
			linea += arreglo[i] + " ";
			if (acumulatedChar >= MaxCharacterPerLine) {
				respuesta.add(linea);
				linea = "";
				acumulatedChar = 0;
			}
		}
		if (acumulatedChar > 0) {
			respuesta.add(linea);
		}
		return respuesta;
	}

	@Override
	public void mover(int distX, int distY) {
		Anchor.x += distX;
		Anchor.y += distY;
		for (Componente value : _subComponentes) {
			((CompLifeBar)value).moverTodo(distX, distY);
		}
		actualizarPuntoCentral();
		actualizarAchorsPoints();
	}

	@Override
	public String getTipo() {
		return "Objeto";
	}
	
	public void aumentarBaseLine(){
		baseLineHeight += SizeSteeps;
		actualizarPuntoCentral();
	}
	
	public void reducirBaseLine(){
		baseLineHeight -= SizeSteeps;
		if(baseLineHeight < MinBaseLineHeight){
			baseLineHeight = MinBaseLineHeight;
		}
		actualizarPuntoCentral();
	}
	
	public void agregarLifeTime(CompLifeBar nuevo){
		int initialPointX = _centerPoint.x;
		int initialPointY = lowerPointY()+InitialBarDistance;
		nuevo.setInitialPos(initialPointX, initialPointY);
		int barSpan = (initialPointY+CompLifeBar.INITIAL_HEIGHT) - (int) (_centerPoint.y+(_height/2));
		if(baseLineHeight < barSpan){
			baseLineHeight = barSpan + InitialBarDistance;
		}
		nuevo.setBounds((int)(Anchor.y+_height),(int)(Anchor.y+_height+baseLineHeight));
		_subComponentes.add(nuevo);
	}
	
	private int lowerPointY(){
		int respuesta = (int) (_centerPoint.y+(_height/2));
		for (Componente value : _subComponentes) {
			if((value.get_centerPoint().y + (value.get_height()/2)) > respuesta){
				respuesta = (int) (value.get_centerPoint().y + (value.get_height()/2));
			}
		}
		return respuesta;
	}
	
	@Override
	public void set_currentState(int _currentState) {
		this._currentState = _currentState;
		for (Componente value : _subComponentes) {
			value.set_currentState(_currentState);
		}
	}
	
	public void removeFocus() {
		_currentState = IDLE;
		for (Componente value : _subComponentes) {
			value.removeFocus();
		}
	}
	
	@Override
	public float get_height(){
		return _height + baseLineHeight;
	}
	
	public Componente checkChildsID(int ID){
		for (Componente value : _subComponentes) {
			if(value.getID() == ID){
				return value;
			}
		}
		return null;
	}

	public int getBaseLineHeight() {
		return baseLineHeight;
	}

	public void setBaseLineHeight(int baseLineHeight) {
		this.baseLineHeight = baseLineHeight;
	}
	
	public void addLifeBar(CompLifeBar nuevo){
		_subComponentes.add(nuevo);
	}
}
